#include "Client.h"

#include "SavingsAccount.h"
#include "CurrentAccount.h"


int Client::clientIDGenerator = 0;

Client::Client(const string firstName,const  string lastName, int age, eGender gender, const Contact& contact)
	: Person(firstName, lastName, age, gender), 
	  clientId(Client::clientIDGenerator++), 
	  contact(contact),
	  isVip(false)
{
	currentAccount = NULL;
}

void Client::setVipStatus(bool isVip)
{
	this->isVip = isVip;
}

int Client::getId() const
{
	return clientId;
}

const Account* Client::getCurrentAccount() const
{
	return this->currentAccount;
}

const SavingsAccount& Client::getSavingsAccount(int accountId) const
{
	vector<SavingsAccount*>::const_iterator	itAccounts;
	for (itAccounts = savingsAccounts.begin(); itAccounts != savingsAccounts.end(); ++itAccounts)
	{
		if ((**itAccounts).getAccountId() == accountId)
		{
			return **itAccounts;
		}
	}

	throw std::exception("Saving account has not been found.");
}

const vector<SavingsAccount*>	Client::getAllSavingsAccounts() const 
{
	return savingsAccounts;
}

bool Client::getVipStatus()	const
{
	return this->isVip;
}

double Client::getTotalMoney()						const
{
	double retTotalMoney = 0;

	vector<SavingsAccount*>::const_iterator	itAccounts;
	for (itAccounts = savingsAccounts.begin(); itAccounts != savingsAccounts.end(); ++itAccounts)
	{
		retTotalMoney += (**itAccounts).getBalance();
	}

	if (currentAccount != NULL)
	{
		retTotalMoney += currentAccount->getBalance();
	}

	return retTotalMoney;
}

void Client::updateCurrentAccount(Account& currAccount)
{
	removeCurrentAccount();
	currentAccount = &currAccount;
}

void Client::addSavingAccount(SavingsAccount* account)
{
	if (isVip)
	{
		vector<SavingsAccount*>::const_iterator	itAccounts = savingsAccounts.begin();
		savingsAccounts.insert(itAccounts, account);
	}
	else
	{
		throw new exception("ERROR: Acount is not VIP.");
	}
}

void Client::removeSavingAccount(int accountId)
{
	SavingsAccount* account = NULL;
	vector<SavingsAccount*>::const_iterator	itAccounts;
	vector<SavingsAccount*>::const_iterator	itAccDelete;

	for (itAccounts = savingsAccounts.begin(); itAccounts != savingsAccounts.end() && account == NULL; ++itAccounts)
	{
		if ((**itAccounts).getAccountId() == accountId)
		{
			account		=  *itAccounts;
			itAccDelete = itAccounts;
		}
	}

	if (account != NULL)
	{
		savingsAccounts.erase(itAccDelete);
		delete account;
	}
	else
	{
		throw ("Saving account has not been found.");
	}

}

bool Client::removeCurrentAccount()
{
	if (currentAccount != NULL)
	{
		delete currentAccount;

		return true;
	}

	return false;
}

void Client::toOs(ostream& os, bool isFullPrint)			const
{
	os << "Client={id=" << clientId << ", Total money=" << getTotalMoney() << ", Is VIP=" << isVip << "\n\t";
	Person::toOs(os);
	os << "\n\t";
	os << contact << endl;
	if (currentAccount != NULL)
	{
		os << "\n\t" << *currentAccount;
		os << endl;
	}

	vector<SavingsAccount*>::const_iterator	itAccounts;
	for (itAccounts = savingsAccounts.begin(); itAccounts != savingsAccounts.end(); ++itAccounts)
	{
		os << **itAccounts << endl;
	}

	os << "}";
}

bool Client::operator==(const Client& other)	const
{
	return (this->clientId == other.clientId) ? true : false;
}

void Client::addTransaction(Transaction& transaction)
{
	CurrentAccount* account = dynamic_cast<CurrentAccount*>(currentAccount);

	if (account != NULL)
	{
		account->addTransaction(transaction);
	}
	else
	{
		throw std::exception("No current account found.");
	}
}

Client::~Client()
{
	SavingsAccount* ptrSavingAccount = NULL;

	vector<SavingsAccount*>::const_iterator	itAccounts;
	for (itAccounts = savingsAccounts.begin(); itAccounts != savingsAccounts.end(); ++itAccounts)
	{
		ptrSavingAccount = *itAccounts;

		delete ptrSavingAccount;
	}

	savingsAccounts.clear();

	delete currentAccount;
}